/**
 * HTTP请求封装工具
 * 参考标准规范，支持Promise和async/await
 */

// 根据环境获取基础URL
const getBaseUrl = () => {
  // 在uni-app中获取环境版本
  let baseUrl = 'https://m.donglem.com/servicehost'

  // 如果是开发环境，可以在这里配置不同的地址
  // #ifdef MP-WEIXIN
  try {
    const accountInfo = wx.getAccountInfoSync()
    const envVersion = accountInfo.miniProgram.envVersion

    const urlConfig = {
      develop: 'https://m.donglem.com/servicehost', // 开发版
      trial: 'https://m.donglem.com/servicehost', // 体验版
      release: 'https://m.donglem.com/servicehost' // 正式版
    }

    baseUrl = urlConfig[envVersion] || baseUrl
  } catch (error) {
    console.warn('获取环境版本失败，使用默认地址')
  }
  // #endif

  return baseUrl
}

export default {
  // 全局配置
  config: {
    baseUrl: getBaseUrl(),
    header: {
      // 默认Content-Type，POST请求会被覆盖为form-data格式
      'Content-Type': 'application/json;charset=UTF-8'
    },
    timeout: 10000,
    dataType: 'json'
  },

  /**
   * 核心请求方法
   * @param {Object} options 请求配置
   */
  request(options = {}) {
    // 处理请求数据和请求头
    let requestData = options.data || {}
    let requestHeader = { ...this.config.header, ...options.header }

    // 如果是POST请求且不是文件上传，转换为FormData格式
    if ((options.method === 'POST' || !options.method) && !options.isFileUpload) {
      // 设置FormData请求头
      requestHeader['Content-Type'] = 'application/x-www-form-urlencoded'

      // 将对象转换为FormData字符串
      if (typeof requestData === 'object' && requestData !== null) {
        const formDataArray = []
        for (const key in requestData) {
          if (Object.prototype.hasOwnProperty.call(requestData, key)) {
            const value = requestData[key]
            if (value !== null && value !== undefined) {
              formDataArray.push(`${encodeURIComponent(key)}=${encodeURIComponent(value)}`)
            }
          }
        }
        requestData = formDataArray.join('&')
      }
    }

    // 组织请求参数
    const requestOptions = {
      url: this.config.baseUrl + options.url,
      method: options.method || 'POST',
      data: requestData,
      header: requestHeader,
      timeout: options.timeout || this.config.timeout,
      dataType: options.dataType || this.config.dataType
    }

    // 微信小程序中启用Cookie支持
    // #ifdef MP-WEIXIN
    requestOptions.enableCookie = true
    // #endif

    // 手动添加Cookie（如果存在）
    const sessionId = this.getSessionId()
    if (sessionId) {
      requestOptions.header.Cookie = `JSESSIONID=${sessionId}`
    }

    console.log('HTTP请求:', requestOptions)

    return new Promise((resolve, reject) => {
      uni.request({
        ...requestOptions,
        success: (result) => {
          console.log('HTTP响应:', result)

          // 提取并保存SessionId
          this.extractAndSaveSessionId(result)

          // HTTP状态码检查
          if (result.statusCode !== 200) {
            const error = {
              code: result.statusCode,
              message: '网络请求失败',
              data: result.data
            }

            if (!options.hideErrorToast) {
              uni.showToast({
                title: error.message,
                icon: 'none'
              })
            }

            return reject(error)
          }

          // 业务状态码处理
          const responseData = result.data

          // 懂了么接口规范：通过statusCode判断成功与否
          // statusCode为"200"表示成功，其他值表示失败
          if (responseData.statusCode === '200' || responseData.statusCode === 200) {
            // 成功
            resolve(responseData)
          } else {
            // 失败
            const error = {
              code: responseData.statusCode || responseData.msgCode || -1,
              message: responseData.message || responseData.msg || '请求失败',
              data: responseData
            }

            if (!options.hideErrorToast) {
              uni.showToast({
                title: error.message,
                icon: 'none'
              })
            }

            reject(error)
          }
        },
        fail: (error) => {
          console.error('HTTP请求失败:', error)

          const failError = {
            code: -1,
            message: '网络连接失败',
            data: error
          }

          if (!options.hideErrorToast) {
            uni.showToast({
              title: failError.message,
              icon: 'none'
            })
          }

          reject(failError)
        }
      })
    })
  },

  /**
   * GET请求
   * @param {String} url 请求地址
   * @param {Object} data 请求参数
   * @param {Object} options 额外配置
   */
  get(url, data = {}, options = {}) {
    return this.request({
      url,
      method: 'GET',
      data,
      ...options
    })
  },

  /**
   * POST请求（默认使用FormData格式）
   * @param {String} url 请求地址
   * @param {Object} data 请求参数
   * @param {Object} options 额外配置
   */
  post(url, data = {}, options = {}) {
    return this.request({
      url,
      method: 'POST',
      data,
      ...options
    })
  },

  /**
   * POST请求（使用JSON格式）
   * @param {String} url 请求地址
   * @param {Object} data 请求参数
   * @param {Object} options 额外配置
   */
  postJson(url, data = {}, options = {}) {
    return this.request({
      url,
      method: 'POST',
      data,
      isFileUpload: true, // 标记为文件上传，保持JSON格式
      ...options
    })
  },

  /**
   * PUT请求
   * @param {String} url 请求地址
   * @param {Object} data 请求参数
   * @param {Object} options 额外配置
   */
  put(url, data = {}, options = {}) {
    return this.request({
      url,
      method: 'PUT',
      data,
      ...options
    })
  },

  /**
   * DELETE请求
   * @param {String} url 请求地址
   * @param {Object} data 请求参数
   * @param {Object} options 额外配置
   */
  delete(url, data = {}, options = {}) {
    return this.request({
      url,
      method: 'DELETE',
      data,
      ...options
    })
  },

  /**
   * 获取存储的token
   */
  getToken() {
    try {
      return uni.getStorageSync('token') || ''
    } catch (error) {
      console.warn('获取token失败:', error)
      return ''
    }
  },

  /**
   * 设置token
   * @param {String} token
   */
  setToken(token) {
    try {
      uni.setStorageSync('token', token)
    } catch (error) {
      console.error('设置token失败:', error)
    }
  },

  /**
   * 清除token
   */
  clearToken() {
    try {
      uni.removeStorageSync('token')
    } catch (error) {
      console.error('清除token失败:', error)
    }
  },

  /**
   * 从响应头中提取并保存SessionId
   * @param {Object} result HTTP响应结果
   */
  extractAndSaveSessionId(result) {
    try {
      const setCookieHeader = result.header['Set-Cookie'] || result.header['set-cookie']
      if (setCookieHeader) {
        // 处理Set-Cookie可能是数组或字符串的情况
        const cookies = Array.isArray(setCookieHeader) ? setCookieHeader : [setCookieHeader]

        for (const cookie of cookies) {
          // 匹配JSESSIONID
          const match = cookie.match(/JSESSIONID=([^;]+)/)
          if (match) {
            const sessionId = match[1]
            this.setSessionId(sessionId)
            console.log('保存SessionId:', sessionId)
            break
          }
        }
      }
    } catch (error) {
      console.warn('提取SessionId失败:', error)
    }
  },

  /**
   * 获取存储的SessionId
   */
  getSessionId() {
    try {
      return uni.getStorageSync('sessionId') || ''
    } catch (error) {
      console.warn('获取SessionId失败:', error)
      return ''
    }
  },

  /**
   * 设置SessionId
   * @param {String} sessionId
   */
  setSessionId(sessionId) {
    try {
      uni.setStorageSync('sessionId', sessionId)
    } catch (error) {
      console.error('设置SessionId失败:', error)
    }
  },

  /**
   * 清除SessionId
   */
  clearSessionId() {
    try {
      uni.removeStorageSync('sessionId')
    } catch (error) {
      console.error('清除SessionId失败:', error)
    }
  }
}

